package com.kiven.operator;

/**
 * equals和==的区别
 * ==运算符：
 * 		比较的是内存堆栈中的值是否相同。如果对于基础类型的数据，它们的值直接存放在内存堆栈中，这些值就可以直接用==进行比较判断它们之间是否相同。
 * 如果比较的是引用类型，那么该引用类型的值是存放在内存的堆(heap)中，然而该引用类型在堆栈(stack)中存放的是该对象所在堆中的地址，如果两个引用类
 * 型变量,执行==比较之后相等，那么证明，这两个引用类型变量所指的内存堆地址相同，也就是说，指向了一个对象。
 * 
 * equals运算符：
 * 		主要针对的是对象之间的比较，在Object超类里的equals比较的也是用==(查看Object.equals()的源码)。一般的类都重写了equals方法。
 * 		两个引用类型变量中所对应的堆的内容相同，则结果就为true。这里无须指向堆(heap)同一个物理地址上的值，只要堆(heap)中存放的值相同即可。
 * @author kivenLi
 *
 */

public class EqualsAnder {
	public static void main(String[] args) {
		/**
		 * 第一种情况：
		String s1 = "kiven";
		String s2 = "kiven";
		System.out.println("s1==s2: " + (s1==s2));
		System.out.println("s1.equals(s2): " + s1.equals(s2));
		//这里只创建一个对象，而s1和s2都是指向同一个String对象"kiven"
		运行结果：
			s1==s2: true  //由于在创建String对象时用String s = "xxxx";方式所创建的String都会放在一个String池里面，类似线程池，
		   				  //当程序再用String s = "xxxx"去创建对象时，则该程序就先到String池中去找，如果找到就直接赋给所创建的对象，而不去内存heap创建出来
			s1.equals(s2): true
		 */
		
		
		/**
		 * 第二种情况：
		String s1 = "kiven";
		String s2 = new String("kiven");//明确告诉虚拟机，要在heap创建一个新的对象
		System.out.println("s1==s2: " + (s1==s2));
		System.out.println("s1.equals(s2): " + s1.equals(s2));
		//这里创建的对象是两个
		运行结果：
			s1==s2: false  //由于s2是新new出来的String类型，堆里面存放的值相同，但是s1和s2两者的存放在堆中的物理地址已经变了。
			s1.equals(s2): true
		*/
		
		/**
		 * 第三种情况：(字符串的方法intern()，该方法操作之后的效果)
		 
		String s1 = "kiven";
		
		// 用intern()方法去new对象时，虚拟机会做一个小操作，就是先去String池中找，如果找到要创建对象所对应的值，那么直接就赋值给这个对象，
		//  如果String池中没有的话，就创建新的，并且将该对象放在String池中。
		String s2 = new String("kiven").intern();
		
		//对上面做稍微改变
		
		String s3 = new String("tantan").intern();
		String s4 = "tantan";
		
		String s5 = new String("liqingwen").intern();
		String s6 = new String("liqingwen").intern();
		
		System.out.println("s1==s2: " + (s1==s2));
		System.out.println("s1.equals(s2): " + s1.equals(s2));
		
		System.out.println("s3==s4: " + (s3==s4));
		System.out.println("s3.equals(s4): " + s3.equals(s4));
		
		System.out.println("s5==s6: " + (s5==s6));
		System.out.println("s5.equals(s6): " + s5.equals(s6));
		
		运行结果
			s1==s2: true
			s1.equals(s2): true
			
			s3==s4: true
			s3.equals(s4): true
			
			s5==s6: true
			s5.equals(s6): true
		*/
		
		String s1 = new String("kiven").intern();
		String s2 = new String("kiven").intern();
		System.out.println("s1==s2: " + (s1==s2));
		System.out.println("s1.equals(s2): " + s1.equals(s2));
	}
}
